package element.synt;

import ast.AstItem;
import ast.ComplexDataSignature;
import ast.DataSignature;
import ast.PrimaryDataSignature;
import element.base.Synt;

import java.util.List;

public class LVal extends Synt {
    @Override
    public AstItem toAst() {
        PrimaryDataSignature base = new PrimaryDataSignature();
        base.name = findFirst().getContent();
        base.type = DataSignature.DataType.PRIMARY;

        ComplexDataSignature data = new ComplexDataSignature();
        data.type = DataSignature.DataType.COMPLEX;

        if (getNodes().size() == 1) {
            return base;
        }

        int point = 1;

        if (getNodes().size() > point) {
            if (getNodes().get(point).isSynt(ArrayPFix.class)) {
                ArrayPFix arrayPFix = (ArrayPFix) getNodes().get(point);
                List<AstItem> indexes = arrayPFix.toAsts();
                if (data.opType == null) {
                    data.dataOperated = base;
                } else {
                    ComplexDataSignature _data = data;
                    data = new ComplexDataSignature();
                    data.dataOperated = _data;
                    data.type = DataSignature.DataType.COMPLEX;
                }
                data.opType = ComplexDataSignature.operationType.ARRAY_LOC;
                for (AstItem item: indexes) {
                    data.operation.add(item);
                }
                point++;
            }
        }

        if (getNodes().size() > point) {
            if (getNodes().get(point).isSynt(ClassPFix.class)) {
                ClassPFix classPFix = (ClassPFix) getNodes().get(point);
                LVal pFix = (LVal) classPFix.getNodes().getLast();

                DataSignature pFixData = (DataSignature) pFix.toAst();
                if (pFixData.type == DataSignature.DataType.PRIMARY) {
                    if (data.opType == null) {
                        data.dataOperated = base;
                    } else {
                        ComplexDataSignature _data = data;
                        data = new ComplexDataSignature();
                        data.dataOperated = _data;
                        data.type = DataSignature.DataType.COMPLEX;
                    }
                    data.opType = ComplexDataSignature.operationType.CLASS_ATTR;
                    data.operation.add(pFixData);
                } else {
                    DataSignature pFixHead = ((ComplexDataSignature) pFixData).dataOperated;
                    ComplexDataSignature tmpData = (ComplexDataSignature) pFixData;

                    while (pFixHead instanceof ComplexDataSignature) {
                        tmpData = (ComplexDataSignature) pFixHead;
                        pFixHead = tmpData.dataOperated;
                    }

                    if (data.opType == null) {
                        data.dataOperated = base;
                    } else {
                        ComplexDataSignature _data = data;
                        data = new ComplexDataSignature();
                        data.dataOperated = _data;
                        data.type = DataSignature.DataType.COMPLEX;
                    }
                    data.opType = ComplexDataSignature.operationType.CLASS_ATTR;
                    data.operation.add(pFixHead);
                    tmpData.dataOperated = data;
                    data = (ComplexDataSignature) pFixData;
                }
                point++;
            }
        }

        return data;
    }
}
